/**
 * Copyright (c) 2011-2016, hubin (jobob@qq.com).
 * <p>
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not
 * use this file except in compliance with the License. You may obtain a copy of
 * the License at
 * <p>
 * http://www.apache.org/licenses/LICENSE-2.0
 * <p>
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
 * License for the specific language governing permissions and limitations under
 * the License.
 */
package com.sigmatrix.h5.service.v2;

import java.io.Serializable;
import java.util.List;

import org.apache.ibatis.session.SqlSession;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;

import com.baomidou.mybatisplus.enums.SqlMethod;
import com.baomidou.mybatisplus.mapper.SqlHelper;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.baomidou.mybatisplus.plugins.Page;
import com.baomidou.mybatisplus.toolkit.ReflectionKit;
import com.sigmatrix.h5.mapper.XBaseMapper;

/**
 * <p>
 * IService 实现类（ 泛型：M 是 mapper 对象，T 是实体 ， PK 是主键泛型 ）
 * </p>
 */
public class CommonDBService<M extends XBaseMapper<T>, T> implements IDBService<T> {

	@Autowired
	protected M baseMapper;

	/**
	 * <p>
	 * 判断数据库操作是否成功
	 * </p>
	 * <p>
	 * 注意！！ 该方法为 Integer 判断，不可传入 int 基本类型
	 * </p>
	 *
	 * @param result
	 *            数据库操作返回影响条数
	 * @return boolean
	 */
	protected static boolean retBool(Integer result) {
		return SqlHelper.retBool(result);
	}

	@SuppressWarnings("unchecked")
	protected Class<T> currentModelClass() {
		return ReflectionKit.getSuperClassGenricType(getClass(), 1);
	}

	/**
	 * <p>
	 * 批量操作 SqlSession
	 * </p>
	 */
	protected SqlSession sqlSessionBatch() {
		return SqlHelper.sqlSessionBatch(currentModelClass());
	}

	/**
	 * 获取SqlStatement
	 *
	 * @param sqlMethod
	 * @return
	 */
	protected String sqlStatement(SqlMethod sqlMethod) {
		return SqlHelper.table(currentModelClass()).getSqlStatement(sqlMethod.getMethod());
	}

	@Transactional(rollbackFor = Exception.class)
	@Override
	public boolean insert(T entity) {
		if (entity == null) {
			throw new RuntimeException("entity 不能为空");
		}
		return retBool(baseMapper.insert(entity));
	}

	@Transactional(rollbackFor = Exception.class)
	@Override
	public boolean insertAllColumn(T entity) {
		if (entity == null) {
			throw new RuntimeException("entity 不能为空");
		}
		return retBool(baseMapper.insertAllColumn(entity));
	}

	@Transactional(rollbackFor = Exception.class)
	@Override
	public boolean deleteById(Serializable id, String tablePrefix) {
		if (id == null) {
			throw new RuntimeException("id 不能为空");
		}
		return SqlHelper.delBool(baseMapper.deleteById(id, tablePrefix));
	}

	@Transactional(rollbackFor = Exception.class)
	@Override
	public boolean updateById(T entity) {
		if (entity == null) {
			throw new RuntimeException("entity 不能为空");
		}
		return retBool(baseMapper.updateById(entity));
	}

	@Transactional(rollbackFor = Exception.class)
	@Override
	public boolean updateAllColumnById(T entity) {
		if (entity == null) {
			throw new RuntimeException("entity 不能为空");
		}
		return retBool(baseMapper.updateAllColumnById(entity));
	}

	@Override
	public T selectById(Serializable id, String tablePrefix) {
		return baseMapper.selectById(id, tablePrefix);
	}

	@Override
	public int selectCount(Wrapper<T> wrapper) {
		if (wrapper == null || wrapper.getEntity() == null) {
			throw new RuntimeException("wrapper 不能为空");
		}
		return SqlHelper.retCount(baseMapper.selectCount(wrapper));
	}

	@Override
	public List<T> selectList(Wrapper<T> wrapper) {
		if (wrapper == null || wrapper.getEntity() == null) {
			throw new RuntimeException("wrapper 不能为空");
		}
		return baseMapper.selectList(wrapper);
	}

	@SuppressWarnings("unchecked")
	@Override
	public Page<T> selectPage(Page<T> page, Wrapper<T> wrapper) {
		if (wrapper == null || wrapper.getEntity() == null) {
			throw new RuntimeException("wrapper 不能为空");
		}
		if (page == null) {
			throw new RuntimeException("page 不能为空");
		}
		wrapper = (Wrapper<T>) SqlHelper.fillWrapper(page, wrapper);
		page.setRecords(baseMapper.selectPage(page, wrapper));
		return page;
	}
}
